#include "mainwindow.h"
#include "ui_mainwindow.h"

MainWindow::MainWindow(QWidget *parent)
    : QMainWindow(parent)
    , ui(new Ui::MainWindow)
{
    ui->setupUi(this);

    menuTable=TD_MENU;
    statementTable=REF_STATEMENT;

    queryWidget=nullptr;
    entityEditor=nullptr;
    logViewer=new LogViewer(this);
    connect(this,&MainWindow::appendLog,
            logViewer,&LogViewer::appendLog);

    startUp();
}

MainWindow::~MainWindow()
{
    delete ui;
}

void MainWindow::startUp()
{
    if(!initializeMySQL())
    {
        QMessageBox::critical(this,"致命错误","无法连接到【MYSQL】！");
        return;
    }
    if(!initializeODBC())
    {
        QMessageBox::critical(this,"致命错误","无法连接到【ODBC】！");
        return;
    }

    prepareMenubar();
}

void MainWindow::prepareMenubar()
{
    if(mysql.isOpen())
    {
        updateQueryMenu();
    }
}

void MainWindow::updateQueryMenu()
{
    if(!ui->menuQuery->isEmpty())
    {
        ui->menuQuery->disconnect();
        ui->menuQuery->clear();
    }

    if(!queryMenuCache.isEmpty())
        queryMenuCache.clear();

    QSqlQuery query(mysql);
    QString sql=QString("select label,detail from %1 where category='%2' order by seq")
            .arg(menuTable)
            .arg("Query");
    emit appendLog(sql);

    query.exec(sql);
    while (query.next()) {
        auto label=query.value(0).toString();
        auto detail=query.value(1).toString();
        ui->menuQuery->addAction(label);
        queryMenuCache.insert(label,detail);
    }

    if(!queryMenuCache.isEmpty())
        connect(ui->menuQuery,&QMenu::triggered,
                this,&MainWindow::processQueryMenu);
}

QMap<QString,QString> MainWindow::fetchStatement(const QString &entry)
{
    QMap<QString,QString> map;
    QSqlQuery query(mysql);
    QString sql=QString("select label,detail from %1 where entry='%2'")
            .arg(statementTable)
            .arg(entry);
    emit appendLog(sql);

    query.exec(sql);
    while (query.next()) {
        auto label=query.value(0).toString();
        auto detail=query.value(1).toString();
        map.insert(label,detail);
    }
    return map;
}

void MainWindow::processQueryMenu(QAction *action)
{
    if(queryMenuCache.contains(action->text()))
    {
        auto entry=queryMenuCache.value(action->text());
        prepareQueryWidget(entry);
    }
}

void MainWindow::prepareQueryWidget(const QString &entry)
{
    if(queryWidget == nullptr)
    {
        queryWidget=new QueryWidget(this,odbc);
        connect(queryWidget,&QueryWidget::showMessage,
                this,&MainWindow::showMessage);
        connect(queryWidget,&QueryWidget::transferLog,
                logViewer,&LogViewer::appendLog);
    }

    if(centralWidget() != queryWidget)
        setCentralWidget(queryWidget);

    auto statements=fetchStatement(entry);
    queryWidget->prepareStatement(statements);
}

void MainWindow::showMessage(const QString &message)
{
    ui->statusbar->showMessage(message,6000);
}

bool MainWindow::initializeMySQL()
{
    mysql = getConnectionFromSHM(SHM_KEY,"u8","mysql_connection");
    if(!mysql.isValid())
        return false;

    if(mysql.open())
        return true;
    else
    {
        qDebug() << mysql.lastError().text();
        return false;
    }
}

bool MainWindow::initializeODBC()
{
    odbc = odbc_getConnectionFromSHM(SHM_KEY,"u8.odbc","odbc_connection");
    if(!odbc.isValid())
        return false;

    if(odbc.open())
        return true;
    else
    {
        qDebug() << odbc.lastError().text();
        return false;
    }
}

void MainWindow::on_actionLogViewer_triggered()
{
    if(logViewer->isHidden())
        logViewer->show();
}

void MainWindow::on_actionEntityEditor_triggered()
{
    if(entityEditor == nullptr)
        entityEditor=new EntityEditor(this,mysql);
    entityEditor->show();
}
